/* Copyright 2011 Brian Cairns
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package net.wsnetwork.reforger;
import java.util.Map;
import java.util.Map.Entry;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

final public class StatVector {
    public static final StatVector ZERO_VECTOR = new StatVector();
    private final int[] data;

    /**
     * Constructs a {@link StatVector} with all values set to 0.
     */
    public StatVector() {
        data = new int[Stat.possibleStats.length];
    }

    public StatVector(int hit, int mst, int hst, int exp, int cri) {
        data = new int[Stat.possibleStats.length];
        data[Stat.hit.getIndex()] = hit;
        data[Stat.mst.getIndex()] = mst;
        data[Stat.hst.getIndex()] = hst;
        data[Stat.exp.getIndex()] = exp;
        data[Stat.cri.getIndex()] = cri;
    }
    
    public StatVector(indzcraft.loader.Item item) {
        data = new int[Stat.possibleStats.length];
        data[Stat.hit.getIndex()] = item.getHit();
        data[Stat.mst.getIndex()] = item.getMastery();
        data[Stat.hst.getIndex()] = item.getHaste();
        data[Stat.exp.getIndex()] = item.getExp();
        data[Stat.cri.getIndex()] = item.getCrit();
    }

    public StatVector(Stat from, Stat to, int delta) {
        data = new int[Stat.possibleStats.length];
        for (Stat stat : Stat.possibleStats) {
            data[stat.getIndex()] = 0;
        }
        data[to.getIndex()] = delta;
        data[from.getIndex()] = -1 * delta;
    }

    public StatVector(Map<Stat, Integer> values) {
        data = new int[Stat.possibleStats.length];
        for (Entry<Stat, Integer> entry : values.entrySet()) {
            data[entry.getKey().getIndex()] = entry.getValue();
        }
    }

    public StatVector(String wowheadData) {
        data = new int[Stat.possibleStats.length];
        for (Stat stat : Stat.possibleStats) {
            Pattern pattern = Pattern.compile("\"" + stat.getWowheadName() + "\":(\\d+)");
            Matcher matcher = pattern.matcher(wowheadData);
            if (matcher.find()) {
                data[stat.getIndex()] = Integer.parseInt(matcher.group(1));
            } else {
                data[stat.getIndex()] = 0;
            }
        }
    }

    private StatVector(int data[]) {
        this.data = data;
    }

    public StatVector add(StatVector other) {
        int newData[] = new int[Stat.possibleStats.length];
        for (int i = 0; i < newData.length; ++i) {
            newData[i] = data[i] + other.data[i];
        }
        return new StatVector(newData);
    }

    public StatVector subtract(StatVector other) {
        int newData[] = new int[Stat.possibleStats.length];
        for (int i = 0; i < newData.length; ++i) {
            newData[i] = data[i] - other.data[i];
        }
        return new StatVector(newData);
    }

    public int[] getData() {
        return data.clone();
    }

    public int getStat(Stat stat) {
        return data[stat.getIndex()];
    }

    @Override public String toString() {
        StringBuilder builder = new StringBuilder();
        boolean first = true;
        builder.append("[");
        for (Stat stat : Stat.possibleStats) {
            if (!first) {
                builder.append(" ");
            }
            first = false;
            builder.append(stat.getName());
            builder.append("=");
            builder.append(data[stat.getIndex()]);
        }
        builder.append("]");

        return builder.toString();
    }

    @Override public boolean equals(Object other) {
        if (!(other instanceof StatVector)) { return false; }
        StatVector o = (StatVector) other;
        for (int i = 0; i < o.data.length; ++i) {
            if (data[i] != o.data[i]) { return false; }
        }
        return true;
    }
}